#include "RingQueue.hpp"
#include <sys/types.h>
#include <unistd.h>
#include "Task.hpp"

string ThreadName()
{
    char name[1024];
    snprintf(name, sizeof name, "thread[0x%x]", pthread_self());
    return name;
}

void *productor_routine(void *args)
{
    RingQueue<CalTask> *rq = static_cast<RingQueue<CalTask> *>(args);
    while (true)
    {
        // 生产数据
        // int data = rand() % 15 + 1;
        // rq->Push(data);
        // cout << "生产者生产的数据为: " << data << endl;
        // sleep(1); // 生产一个消费一个

        int x = rand() % 10 + 1;
        int y = rand() % 5 + 1;
        char op = opArr[rand() % opArr.size()];
        CalTask ct(x, y, op, mymath);
        rq->Push(ct);
        cout << ThreadName() << "生产者生产的数据为: " << ct.toTaskString() << endl;
        sleep(1);
    }
    return nullptr;
}

void *consumer_routine(void *args)
{
    RingQueue<CalTask> *rq = static_cast<RingQueue<CalTask> *>(args);
    while (true)
    {
        // 消费数据
        // int data;
        // rq->Pop(&data);
        // cout << "消费者消费的数据为: " << data << endl;

        CalTask ct;
        rq->Pop(&ct);
        cout << ThreadName() << "消费者消费的数据为: " << ct() << endl;
    }
    return nullptr;
}

int main()
{
    srand((unsigned int)time(nullptr) ^ getpid() ^ pthread_self() ^ 0x12233445);
    RingQueue<CalTask> *rq = new RingQueue<CalTask>();
    // 单消费，单生产

    //多生产 多消费 需要加锁
    pthread_t p[5], c[10];
    for (int i = 0; i < 5; i++)
    {
        pthread_create(p + i, nullptr, productor_routine, rq);
    }
    for (int i = 0; i < 10; i++)
    {
        pthread_create(c + i, nullptr, consumer_routine, rq);
    }

    for (int i = 0; i < 5; i++)
        pthread_join(p[i], nullptr);
    for (int i = 0; i < 10; i++)
        pthread_join(c[i], nullptr);

    return 0;
}